﻿using System;
using System.Collections.Generic;
using System.Collections.ObjectModel;
using System.ComponentModel;
using System.Linq;
using System.Net;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Ink;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Animation;
using System.Windows.Shapes;
using ConfApp.Infrastructure;
using ConfApp.Models;
using ConfApp.Services;
using Microsoft.Practices.Prism.Commands;

namespace ConfApp.ViewModels
{
    public class SessionListViewModel : ViewModel
    {
        private readonly IConfDataStoreLocator _confDataStoreLocator;

        private ObservableCollection<GroupList<SessionInfoViewModel>> _observableSessionInfoGroups0;
        private CollectionViewSource _sessionInfoGroups0ViewSource;

        private ObservableCollection<GroupList<SessionInfoViewModel>> _observableSessionInfoGroups1;
        private CollectionViewSource _sessionInfoGroups1ViewSource;

        public SessionListViewModel(
            IConfDataStoreLocator confDataStoreLocator,
            INavigationService navigationService)
            : base(navigationService)
        {
            _confDataStoreLocator = confDataStoreLocator;
            Initialize();
        }

        private void Initialize()
        {
            _version = -1;
            //Refresh();

            this.SessionSelectedCommand = new DelegateCommand<SessionInfoViewModel>(
                s =>
                {
                    NavigationService.Navigate(
                        new Uri("/Views/SessionDetailsView.xaml?ID=" + s.ID, UriKind.Relative));
                });

            this.IsBeingActivated();
        }

        private string TrackCodeFilter
        {
            get
            {
                return NavigationService.CurrentSource
                                       .OriginalString.Split('=')[1];
            }
        }

        private int _version;
        private string _lastTrackCode = "-";
        private void Refresh()
        {
            var version = _confDataStoreLocator.GetStore().Version;
            if (version > _version || _lastTrackCode != TrackCodeFilter)
            {
                _version = version;
                _lastTrackCode = TrackCodeFilter;
                _observableSessionInfoGroups0 = new ObservableCollection<GroupList<SessionInfoViewModel>>();
                var sessionInfoViewModelGroups0 =
                    GroupSessions(_confDataStoreLocator.GetStore().GetSessionsByDayIndexAndTrack(0,TrackCodeFilter));
                sessionInfoViewModelGroups0.ForEach(_observableSessionInfoGroups0.Add);

                _sessionInfoGroups0ViewSource = new CollectionViewSource {Source = _observableSessionInfoGroups0};

                _observableSessionInfoGroups1 = new ObservableCollection<GroupList<SessionInfoViewModel>>();
                var sessionInfoViewModelGroups1 =
                    GroupSessions(_confDataStoreLocator.GetStore().GetSessionsByDayIndexAndTrack(1,TrackCodeFilter));
                sessionInfoViewModelGroups1.ForEach(_observableSessionInfoGroups1.Add);

                _sessionInfoGroups1ViewSource = new CollectionViewSource
                                                        {Source = _observableSessionInfoGroups1};
            }
        }

        private List<GroupList<SessionInfoViewModel>> GroupSessions(IEnumerable<Session> sessions)
        {
            var result = new List<GroupList<SessionInfoViewModel>>();
            var slots = sessions.OrderBy(s => s.Slot.Day.Date).ThenBy(s=>s.Slot.ToTimeSpanString()).Select(s => s.Slot.ToTimeSpanString()).Distinct();
            var sessionInfos = sessions.OrderBy(s => s.Slot.Day.Date).ThenBy(s => s.Slot.ToTimeSpanString()).Select(s => new SessionInfoViewModel(s, NavigationService));
            var groups = new Dictionary<string, GroupList<SessionInfoViewModel>>();
            foreach (var slot in slots)
            {
                var group = new GroupList<SessionInfoViewModel>(slot);
                result.Add(group);
                groups[slot] = group;
            }
            foreach (var sessionInfo in sessionInfos)
            {
                groups[sessionInfo.Slot.Trim()].Add(sessionInfo);
            }
            return result;
        }

        public ICollectionView SessionInfos0
        {
            get
            {
                Refresh();
                return _sessionInfoGroups0ViewSource.View;
            }
        }

        public DelegateCommand<SessionInfoViewModel> SessionSelectedCommand { get; set; }

        public ICollectionView SessionInfos1
        {
            get
            {
                Refresh();
                return _sessionInfoGroups1ViewSource.View;
            }
        }

        public override void IsBeingActivated()
        {

        }
    }
}
